Imports System.ComponentModel

Public Class FormMain
    Dim datStart As Date
    Private Sub ButtonSearch_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles ButtonSearch.Click
        If TextBoxArtist.Text.Trim.Length > 1 And TextBoxSong.Text.Trim.Length > 1 Then
            ButtonSearch.Enabled = False
            ButtonSearchText.Enabled = False
            BackgroundWorkerMain.RunWorkerAsync(New SearchParameters(TextBoxArtist.Text.Trim, TextBoxSong.Text.Trim))
        Else
            MsgBox("Please enter an artist and song to search...")
        End If
    End Sub
    Private Sub ButtonSearchText_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles ButtonSearchText.Click
        If TextBoxLyricText.Text.Trim.Length > 1 Then
            ButtonSearch.Enabled = False
            ButtonSearchText.Enabled = False
            BackgroundWorkerMain.RunWorkerAsync(New SearchTextParameters(TextBoxLyricText.Text.Trim))
        Else
            MsgBox("Please enter a song text to search...")
        End If
    End Sub
    Private Sub FormMain_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
        Me.Text = "Chartlyrics Lyrics Application " & My.Application.Info.Version.ToString
        SetupDataGridView()
    End Sub
    Private Sub DataGridViewResults_CellFormatting(ByVal sender As Object, _
        ByVal e As System.Windows.Forms.DataGridViewCellFormattingEventArgs) _
        Handles DataGridViewResults.CellFormatting

        If Me.DataGridViewResults.Columns(e.ColumnIndex).Name = _
            "Release Date" Then

            If e IsNot Nothing Then
                If e.Value IsNot Nothing Then
                    Try
                        e.Value = DateTime.Parse(e.Value.ToString()) _
                            .ToLongDateString()
                        e.FormattingApplied = True
                    Catch ex As FormatException
                        Console.WriteLine("{0} is not a valid date.", e.Value.ToString())
                    End Try
                End If
            End If

        End If

    End Sub
    Private Sub SetupDataGridView()
        DataGridViewResults.ColumnCount = 7
        With DataGridViewResults.ColumnHeadersDefaultCellStyle
            .BackColor = Color.Navy
            .ForeColor = Color.White
            .Font = New Font(DataGridViewResults.Font, FontStyle.Bold)
        End With

        With DataGridViewResults
            .Name = "DataGridViewResults"
            .Location = New Point(8, 8)
            .Size = New Size(500, 250)
            .AutoSizeRowsMode = _
                DataGridViewAutoSizeRowsMode.DisplayedCellsExceptHeaders
            .ColumnHeadersBorderStyle = DataGridViewHeaderBorderStyle.Single
            .CellBorderStyle = DataGridViewCellBorderStyle.Single
            .GridColor = Color.Black
            .RowHeadersVisible = False

            .Columns(0).Name = "lyricChecksum"
            .Columns(1).Name = "lyricId"
            .Columns(2).Name = "songUrl"
            .Columns(3).Name = "artistUrl"
            .Columns(4).Name = "artist"
            .Columns(5).Name = "song"
            .Columns(6).Name = "songRank"

            .SelectionMode = DataGridViewSelectionMode.FullRowSelect
            .MultiSelect = False
            .Dock = DockStyle.Fill
        End With

    End Sub
    Private Sub DataGridViewResults_CellClick(ByVal sender As System.Object, ByVal e As System.Windows.Forms.DataGridViewCellEventArgs) Handles DataGridViewResults.CellClick
        Try
            Dim lyricChecksum As String = String.Empty
            Dim lyricId As Integer = 0
            Dim songUrl As String = String.Empty
            Dim artist As String = String.Empty
            Dim song As String = String.Empty
            If e.RowIndex >= 0 Then
                Dim row As DataGridViewRow = DataGridViewResults.Rows.Item(e.RowIndex)
                For index As Integer = 0 To row.Cells.Count - 1
                    If row.Cells.Item(index).OwningColumn.Name = "lyricChecksum" And row.Cells.Item(index).Value IsNot Nothing Then
                        lyricChecksum = row.Cells.Item(index).Value.ToString
                    End If
                    If row.Cells.Item(index).OwningColumn.Name = "lyricId" And row.Cells.Item(index).Value IsNot Nothing Then
                        lyricId = Convert.ToInt32(row.Cells.Item(index).Value)
                    End If
                    If row.Cells.Item(index).OwningColumn.Name = "songUrl" And row.Cells.Item(index).Value IsNot Nothing Then
                        songUrl = row.Cells.Item(index).Value.ToString
                    End If
                    If row.Cells.Item(index).OwningColumn.Name = "artist" And row.Cells.Item(index).Value IsNot Nothing Then
                        artist = row.Cells.Item(index).Value.ToString
                    End If
                    If row.Cells.Item(index).OwningColumn.Name = "song" And row.Cells.Item(index).Value IsNot Nothing Then
                        song = row.Cells.Item(index).Value.ToString
                    End If
                Next
                If lyricId > 0 Then
                    FormLyric.Visible = True
                    FormLyric.Activate()
                    FormLyric.loadLyric(lyricChecksum, lyricId)
                ElseIf songUrl.Length > 0 Then
                    FormLyric.Visible = True
                    FormLyric.Activate()
                    FormLyric.addLyric(songUrl, artist, song)
                End If
            End If
        Catch ex As Exception
            Throw ex
        End Try
    End Sub
    Private Sub FormDisplayResult(ByVal status As String)
        ToolStripStatusLabelMain.Text = status
    End Sub
    Private Sub UpdateResults(ByVal clsr As ChartlyricsApi.SearchLyricResult())
        Dim ts As TimeSpan = Now.Subtract(datStart)
        FormDisplayResult("Found " & clsr.GetLength(0) & " results in " & ts.TotalSeconds & " seconds...")
        DataGridViewResults.Rows.Clear()
        For Each res As ChartlyricsApi.SearchLyricResult In clsr
            If res IsNot Nothing Then
                Dim row As String() = {res.LyricChecksum, res.LyricId.ToString, res.SongUrl, res.ArtistUrl, res.Artist, res.Song, res.SongRank.ToString}
                DataGridViewResults.Rows.Add(row)
            End If
        Next
    End Sub
#Region "BackGroundWorker"
    Private Sub backgroundWorker_DoWork(ByVal sender As Object, ByVal eventArgs As DoWorkEventArgs) Handles BackgroundWorkerMain.DoWork
        datStart = Now
        Dim bgw As BackgroundWorker = CType(sender, BackgroundWorker)
        bgw.ReportProgress(0, "Searching...")
        Dim slw As New SearchLyricWorker()
        eventArgs.Result = slw.Execute(bgw, eventArgs)
    End Sub
    Private Sub backgroundWorker_ProgressChanged(ByVal sender As Object, ByVal eventArgs As ProgressChangedEventArgs) Handles BackgroundWorkerMain.ProgressChanged
        FormDisplayResult(eventArgs.UserState.ToString())
    End Sub
    Private Sub backgroundWorker_RunWorkerCompleted(ByVal sender As Object, ByVal eventArgs As RunWorkerCompletedEventArgs) Handles BackgroundWorkerMain.RunWorkerCompleted
        If eventArgs.Error IsNot Nothing Then
            MsgBox("backgroundWorker Error " & eventArgs.Error.Message)
        ElseIf eventArgs.Cancelled Then
            FormDisplayResult("backgroundWorker Cancelled")
        Else
            FormDisplayResult("backgroundWorker Completed")
            UpdateResults(CType(eventArgs.Result, ChartlyricsApi.SearchLyricResult()))
        End If
        ButtonSearch.Enabled = True
        ButtonSearchText.Enabled = True
    End Sub
#End Region
#Region "Menu"
    Private Sub ContentsToolStripMenuItem_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles ContentsToolStripMenuItem.Click
        System.Diagnostics.Process.Start(My.Application.Info.CompanyName)
    End Sub

    Private Sub AboutToolStripMenuItem_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles AboutToolStripMenuItem.Click
        AboutBoxMain.Visible = True
        AboutBoxMain.Activate()
    End Sub

    Private Sub ExitToolStripMenuItem_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles ExitToolStripMenuItem.Click
        Me.Close()
    End Sub
#End Region
End Class
Public Class SearchLyricWorker
    Public Sub DisplayResultString(ByRef bgw As BackgroundWorker, ByVal str As String, ByVal percent As Double)
        bgw.ReportProgress(Convert.ToInt32(percent * 100000), str)
    End Sub
    Public Function Execute(ByRef bgw As BackgroundWorker, ByRef e As DoWorkEventArgs) As ChartlyricsApi.SearchLyricResult()
        If TypeOf e.Argument Is SearchParameters Then
            Dim sp As SearchParameters = CType(e.Argument, SearchParameters)
            Try
                Dim clapi As New ChartlyricsApi.apiv1()
                Dim clsr As ChartlyricsApi.SearchLyricResult() = clapi.SearchLyric(sp.Artist, sp.Song)
                Return clsr
            Catch ex As Exception
                Throw ex
            End Try
        ElseIf TypeOf e.Argument Is SearchTextParameters Then
            Dim stp As SearchTextParameters = CType(e.Argument, SearchTextParameters)
            Try
                Dim clapi As New ChartlyricsApi.apiv1()
                Dim clsr As ChartlyricsApi.SearchLyricResult() = clapi.SearchLyricText(stp.LyricText)
                Return clsr
            Catch ex As Exception
                Throw ex
            End Try
        Else
            Throw New Exception("Invalid search type")
        End If
        DisplayResultString(bgw, "Finish " & Now.ToString(), 999)
    End Function
End Class
Public Class SearchParameters
    Sub New(ByVal artist As String, ByVal song As String)
        privArtist = artist
        privSong = song
    End Sub
    Private privSong As String
    Private privArtist As String
    Public Property Song() As String
        Get
            Return privSong
        End Get
        Set(ByVal value As String)
            privSong = value
        End Set
    End Property
    Public Property Artist() As String
        Get
            Return privArtist
        End Get
        Set(ByVal value As String)
            privArtist = value
        End Set
    End Property
End Class
Public Class SearchTextParameters
    Sub New(ByVal lyricText As String)
        privLyricText = lyricText
    End Sub
    Private privLyricText As String
    Public Property LyricText() As String
        Get
            Return privLyricText
        End Get
        Set(ByVal value As String)
            privLyricText = value
        End Set
    End Property
End Class